package base.thread_demo.demo21;

import java.util.concurrent.atomic.AtomicMarkableReference;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * AtomicMarkableReference对中间变动多少次不关心，只关心原子引用共享的变量是否更改过,通过boolean状态标志监视是否中途被修改
 *
 */
public class Demo03 {
	private static final Logger log = LoggerFactory.getLogger(Demo03.class);

	public static void main(String[] args) {
		GarbageBag bag = new GarbageBag("装满垃圾的垃圾袋");
		/*
		 * 将受保护的GarbageBag对象放入AtomicMarkableReference原子引用接口中
		 * 参数2代表bag的原始状态，比如这里代表垃圾袋装满了
		 */
		AtomicMarkableReference<GarbageBag> ref = new AtomicMarkableReference<GarbageBag>(bag, true);

		GarbageBag prev = ref.getReference();
//		log.info("{}", bag==prev);//true
		log.info("{}",prev);

		// 模拟保洁清理垃圾,修改了bag状态
		new Thread(()->{
			bag.setDesc("空垃圾袋");
			//保洁会将垃圾袋清空，然后将状态置为false
			log.info("{}",ref.compareAndSet(bag, bag, true, false));
			log.info("{}", bag);
		},"保洁工").start();

		try {
			Thread.sleep(2000);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}

		log.info("想换一只新垃圾袋？");
		/*
		 * main线程发现prev里面状态是false，与第三个参数true表示的应该是true状态进行判定，结果false≠true，修改失败.
		 */
		boolean success = ref.compareAndSet(prev, new GarbageBag("新垃圾袋"), true, false);
		log.info("换了吗？"+success);
		log.info("{}", ref.getReference());
	}

}

class GarbageBag {
	private String desc;

	public GarbageBag(String desc) {
		this.desc = desc;
	}

	public void setDesc(String desc) {
        this.desc = desc;
    }

	public String toString() {
        return super.toString() + " " + desc;
    }
}
